package lumis.service.wsrp.consumer.doui;

import java.util.Map;

import lumis.doui.source.IDataProvider;
import lumis.doui.source.ISourceData;
import lumis.doui.source.TabularData;
import lumis.doui.source.TabularSource;
import lumis.portal.PortalException;
import lumis.portal.authentication.SessionConfig;
import lumis.util.ITransaction;

/**
 * Abstract class that implements IDataProvider and provides a general 
 * behavior to Key/Value Data Providers.
 * Each row in the TabularData contain only two keys: 'key' and 'value'.  
 * The subclasses of MapDataProvider must only provide the implementation for the 
 * method obtainMapData - that has to return a Map.
 * The MapDataProvider class has the ability to construct the TabularData from 
 * the Map.
 * 
 * @version $Revision: 12680 $ $Date: 2011-03-04 15:32:40 -0300 (Fri, 04 Mar 2011) $
 * @since 5.6.0
 */
public abstract class MapDataProvider implements IDataProvider<TabularSource<?>> 
{
	
	private static final String KEY = "key";
	private static final String VALUE = "value";
	
	public void loadData(SessionConfig sessionConfig, 
						TabularSource<?> source,
						ITransaction transaction) 
				throws PortalException 
	{

		Map<?, ?> mapData = obtainMapData(sessionConfig, source, transaction);
		buildTabularData(mapData, source);
	}
	
	/**
	 * Provides the Map data for each specific implementation  
	 * @param sessionConfig		an instance of SessionConfig
	 * @param source			an instance of TabularSource
	 * @param transaction		the current transaction
	 * @return					an instance of Map with the data to be filled 
	 * 							in TabularData
	 * @throws PortalException	whenever an error occur
	 */
	protected abstract Map<?, ?> obtainMapData(SessionConfig sessionConfig, 
														TabularSource<?> source,
														ITransaction transaction)
												throws PortalException;

	/**
	 * Fill the TabularData from TabularSource using the information in the Map
	 * @param mapData			the Map containing the data
	 * @param source			the TabularSource instance
	 * @throws PortalException	whenever an error occur
	 */
	protected void buildTabularData(Map<?, ?> mapData, 
									TabularSource<?> source) 
					throws PortalException 
	{
		
		TabularData tabularData = source.getData();
		
		ISourceData row;
		for (Object key : mapData.keySet()) {
			row = tabularData.addRow();
			row.put(KEY, key);
			row.put(VALUE, mapData.get(key));
		}
	}
}
